package com.hongzhimei.yukicomic.utils;

import rx.Observable;
import rx.subjects.PublishSubject;
import rx.subjects.SerializedSubject;
import rx.subjects.Subject;

/**
 * Created by wuwei on 2016/12/20.
 * 举例：fragment给activity传递消息
 * ---------------------------------------------------------------
 * 在fragment中调用：
 * RxBus.getDefault().post("这是传给activity的消息");
 * ---------------------------------------------------------------
 * 在activity中通过订阅进行接收：
 * subscription=RxBus.getDefault().toObserverable(String.class)
 *    .subscribe(new Action1<String>() {
 *        @Override
 *        public void call(String s) {
 *               //将接受到的消息打印出来
 *              Toast.makeText(MainActivity.this, s, Toast.LENGTH_LONG).show();
 *              }
 *         }, new Action1<Throwable>() {
 *        @Override
 *        public void call(Throwable throwable) {
 *              //处理异常
 *              }
 *      });
 * ---------------------------------------------------------------
 * 完成后一定要在onDestroy中解除订阅
 * @Override
 * protected void onDestroy() {
 *      super.onDestroy();
 *       //解除订阅
 *      if (subscription != null && subscription.isUnsubscribed()) {
 *                   subscription.unsubscribe();
 *          }
 *      }
 *
 */

public class RxBus {
    private static volatile RxBus defaultInstance;
    // 主题
    private final Subject bus;
    // PublishSubject只会把在订阅发生的时间点之后来自原始Observable的数据发射给观察者
    public RxBus() {
        bus = new SerializedSubject<>(PublishSubject.create());
    }
    // 单例RxBus
    public static RxBus getDefault() {
        RxBus rxBus = defaultInstance;
        if (defaultInstance == null) {
            synchronized (RxBus.class) {
                rxBus = defaultInstance;
                if (defaultInstance == null) {
                    rxBus = new RxBus(); defaultInstance = rxBus;
                }
            }
        }
        return rxBus;
    }
    // 提供了一个新的事件
    public void post (Object o) {
        bus.onNext(o);
    }
    // 根据传递的 eventType 类型返回特定类型(eventType)的 被观察者
    public <T> Observable<T> toObserverable (Class<T> eventType) {
        return bus.ofType(eventType);
    }
}
